/**
 * 地图工具类 - 提供绘制、测量等功能
 */
import { Style, Circle as CircleStyle, Fill, Stroke } from 'ol/style.js';
import { Draw, Modify, Snap } from 'ol/interaction.js';
import Feature from 'ol/Feature.js';
import { Point, LineString, Polygon } from 'ol/geom.js';
import { getArea, getLength } from 'ol/sphere.js';

// 地图实例和数据源
let map: any = null;
let vectorSource: any = null;

// 样式
const defaultStyle = new Style({
  fill: new Fill({
    color: 'rgba(64, 158, 255, 0.2)'
  }),
  stroke: new Stroke({
    color: '#409EFF',
    width: 2
  }),
  image: new CircleStyle({
    radius: 5,
    fill: new Fill({
      color: '#409EFF'
    })
  })
});

/**
 * 设置地图实例
 * @param mapInstance OpenLayers地图实例
 */
function setMap(mapInstance: any): void {
  map = mapInstance;
}

/**
 * 设置矢量数据源
 * @param source 矢量数据源
 */
function setVectorSource(source: any): void {
  vectorSource = source;
}

/**
 * 获取当前矢量数据源
 * @returns 矢量数据源
 */
function getVectorSource(): any {
  return vectorSource;
}

/**
 * 测量线段长度
 * @param geometry 线段几何对象
 * @returns 长度(米)
 */
function getLineLength(geometry: any): number {
  if (!geometry || geometry.getType() !== 'LineString') {
    return 0;
  }
  
  const length = getLength(geometry);
  return length;
}

/**
 * 测量多边形面积
 * @param geometry 多边形几何对象
 * @returns 面积(平方米)
 */
function getPolygonArea(geometry: any): number {
  if (!geometry || geometry.getType() !== 'Polygon') {
    return 0;
  }
  
  const area = getArea(geometry);
  return area;
}

/**
 * 创建绘制工具
 * @param type 绘制类型：Point, LineString, Polygon, Circle
 * @param style 样式
 * @returns 绘制交互
 */
function createDrawInteraction(type: string, style: any = defaultStyle): any {
  if (!map || !vectorSource) {
    return null;
  }

  const draw = new Draw({
    source: vectorSource,
    type: type as any,
    style: style
  });

  return draw;
}

/**
 * 创建修改工具
 * @returns 修改交互
 */
function createModifyInteraction(): any {
  if (!map || !vectorSource) {
    return null;
  }

  const modify = new Modify({
    source: vectorSource
  });

  return modify;
}

/**
 * 添加要素
 * @param feature 要素
 */
function addFeature(feature: any): void {
  if (!vectorSource || !feature) {
    return;
  }

  vectorSource.addFeature(feature);
}

/**
 * 清除所有绘制的要素
 */
function clearFeatures(): void {
  if (!vectorSource) {
    return;
  }

  vectorSource.clear();
}

/**
 * 创建多边形
 * @param coordinates 坐标数组
 * @param style 样式
 * @returns 多边形要素
 */
function createPolygonFeature(coordinates: any[], style: any = defaultStyle): any {
  if (!coordinates || !Array.isArray(coordinates) || coordinates.length < 1) {
    return null;
  }
  
  try {
    const polygon = new Polygon(coordinates);
    const feature = new Feature(polygon);
    feature.setStyle(style);
    return feature;
  } catch (error) {
    return null;
  }
}

/**
 * 创建线段
 * @param coordinates 坐标数组
 * @param style 样式
 * @returns 线段要素
 */
function createLineFeature(coordinates: any[], style: any = defaultStyle): any {
  if (!coordinates || !Array.isArray(coordinates) || coordinates.length < 2) {
    return null;
  }
  
  try {
    const line = new LineString(coordinates);
    const feature = new Feature(line);
    feature.setStyle(style);
    return feature;
  } catch (error) {
    return null;
  }
}

/**
 * 坐标转换为数组格式
 * @param points 点集合 {lng, lat}
 * @returns 坐标数组 [[lng, lat], ...]
 */
function pointsToCoordinates(points: any[]): number[][] {
  if (!points || !Array.isArray(points)) {
    return [];
  }
  
  return points.map(point => {
    if (!point || typeof point.lng === 'undefined' || typeof point.lat === 'undefined') {
      return [0, 0]; // 返回无效坐标点
    }
    return [Number(point.lng), Number(point.lat)]; // 确保坐标为数字
  });
}

/**
 * 验证坐标数组是否有效
 * @param coordinates 坐标数组
 * @returns 是否有效
 */
function isValidCoordinates(coordinates: any[]): boolean {
  if (!coordinates || !Array.isArray(coordinates)) {
    return false;
  }
  
  // 校验每个坐标点
  for (const coord of coordinates) {
    if (!Array.isArray(coord) || coord.length < 2) {
      return false;
    }
    
    if (typeof coord[0] !== 'number' || typeof coord[1] !== 'number') {
      return false;
    }
    
    // 检查经纬度是否在有效范围内
    if (coord[0] < -180 || coord[0] > 180 || coord[1] < -90 || coord[1] > 90) {
      return false;
    }
  }
  
  return true;
}

export default {
  setMap,
  setVectorSource,
  getVectorSource,
  getLineLength,
  getPolygonArea,
  createDrawInteraction,
  createModifyInteraction,
  addFeature,
  clearFeatures,
  createPolygonFeature,
  createLineFeature,
  pointsToCoordinates,
  isValidCoordinates
}; 